package com.example.afinal;

import androidx.annotation.RequiresApi;
import androidx.appcompat.app.AppCompatActivity;

import android.app.DatePickerDialog;
import android.content.ContentValues;
import android.database.Cursor;
import android.database.sqlite.SQLiteDatabase;
import android.graphics.Color;
import android.icu.util.Calendar;
import android.os.Build;
import android.os.Bundle;
import android.util.Log;
import android.view.View;
import android.widget.AdapterView;
import android.widget.Button;
import android.widget.DatePicker;
import android.widget.TextView;
import android.widget.Toast;

import java.util.ArrayList;
import java.util.Collections;
import java.util.List;

import lecho.lib.hellocharts.gesture.ContainerScrollType;
import lecho.lib.hellocharts.gesture.ZoomType;
import lecho.lib.hellocharts.model.Axis;
import lecho.lib.hellocharts.model.AxisValue;
import lecho.lib.hellocharts.model.Line;
import lecho.lib.hellocharts.model.LineChartData;
import lecho.lib.hellocharts.model.PieChartData;
import lecho.lib.hellocharts.model.PointValue;
import lecho.lib.hellocharts.model.SliceValue;
import lecho.lib.hellocharts.model.ValueShape;
import lecho.lib.hellocharts.model.Viewport;
import lecho.lib.hellocharts.util.ChartUtils;
import lecho.lib.hellocharts.view.LineChartView;
import lecho.lib.hellocharts.view.PieChartView;

public class StatActivity extends AppCompatActivity implements View.OnClickListener{
    private LineChartView lineChart;
    private PieChartView pieChart;
    private Button btn_select_type;
    private Button btn_calendar;
    private TextView tv_date;
    private boolean type=true;  //true为支出, false为收入

    MyHelper myHelper;
    private int num = 0;    // 账单数目

    private int num_income = 0;    // 账单数目
    private ArrayList<Integer> years_income =new ArrayList();
    private ArrayList<Integer> months_income =new ArrayList();
    private ArrayList<Integer> dayOfMonths_income =new ArrayList();
    private ArrayList<Integer> types_income = new ArrayList();
    private ArrayList<String> remarks_income = new ArrayList();
    private ArrayList<Float> accounts_income = new ArrayList();

    private int num_outcome = 0;    // 账单数目
    private ArrayList<Integer> years_outcome =new ArrayList();
    private ArrayList<Integer> months_outcome =new ArrayList();
    private ArrayList<Integer> dayOfMonths_outcome =new ArrayList();
    private ArrayList<Integer> types_outcome = new ArrayList();
    private ArrayList<String> remarks_outcome = new ArrayList();
    private ArrayList<Float> accounts_outcome = new ArrayList();

    String[] month = {"1月","2月","3月","4月","5月","6月","7月","8月","9月","10月","11月","12月"};//X轴的标注
    float[] income_month= {0,0,0,0,0,0,0,0,0,0,0,0};//图表的数据点
    float[] outcome_month= {0,0,0,0,0,0,0,0,0,0,0,0};//图表的数据点
    float[] outcome_type= {0,0,0,0,0,0,0,0,0,0,0,0};
    float[] income_type= {0,0,0,0};
    private PieChartData data;         //存放数据
    private List<PointValue> mPointValues = new ArrayList<PointValue>();
    private List<AxisValue> mAxisXValues = new ArrayList<AxisValue>();
    private boolean hasLabels = true;                   //是否有标语
    private boolean hasLabelsOutside = false;           //扇形外面是否有标语
    private boolean hasCenterCircle = false;            //是否有中心圆
    private boolean isExploded = false;                  //是否是炸开的图像
    private boolean hasLabelForSelected = false;         //选中的扇形显示标语
    /*******************    hellochart            ******************/
    /*****************************************************************************/
    @RequiresApi(api = Build.VERSION_CODES.N)
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_stat);
        lineChart = (LineChartView)findViewById(R.id.line_chart);
        pieChart = (PieChartView)findViewById(R.id.pie_chart);
        btn_select_type = findViewById(R.id.btn_select_type);
        btn_calendar = findViewById(R.id.btn_calendar);
        tv_date = findViewById(R.id.tv_date);

        btn_select_type.setOnClickListener(this);
        btn_calendar.setOnClickListener(this);

        GlobalVariables.getCurrentDateActivity();
        updateUI();
    }

    public static float[] resetArray(float[] a){
        float[] b2 = new float[a.length];
        for(int i=0;i<a.length;i++)
        {
            a[i] = b2[i];
        }
        return a;
    }
    private void initDatabase(){
        years_outcome =new ArrayList();
        months_outcome =new ArrayList();
        dayOfMonths_outcome =new ArrayList();
        types_outcome = new ArrayList();
        remarks_outcome = new ArrayList();
        accounts_outcome = new ArrayList();
        years_income =new ArrayList();
        months_income =new ArrayList();
        dayOfMonths_income =new ArrayList();
        types_income = new ArrayList();
        remarks_income = new ArrayList();
        accounts_income = new ArrayList();
        num_outcome=num_income=0;
        resetArray(income_type);
        resetArray(outcome_type);
        resetArray(outcome_month);
        resetArray(income_month);

        myHelper = new MyHelper(this);
        SQLiteDatabase db;
        db = myHelper.getReadableDatabase();
        Cursor cursor = db.query("accountBook", null, null, null, null, null, null);
        num = cursor.getCount();
        if (num != 0) {
            cursor.moveToFirst();
            if(cursor.getInt(4)<20 && GlobalVariables.selectYear==cursor.getInt(1)) {
                outcome_month[cursor.getInt(2)-1]+=cursor.getFloat(5);
                if( GlobalVariables.selectMonth==cursor.getInt(2) ) {
                    years_outcome.add(cursor.getInt(1));
                    months_outcome.add(cursor.getInt(2));
                    dayOfMonths_outcome.add(cursor.getInt(3));
                    types_outcome.add(cursor.getInt(4));
                    accounts_outcome.add(cursor.getFloat(5));
                    remarks_outcome.add(cursor.getString(6));

                    outcome_type[cursor.getInt(4) - 1] += cursor.getFloat(5);
                    num_outcome++;
                }
            }else if(GlobalVariables.selectYear==cursor.getInt(1)){
                income_month[cursor.getInt(2)-1]+=cursor.getFloat(5);
                if(GlobalVariables.selectMonth==cursor.getInt(2)) {
                    years_income.add(cursor.getInt(1));
                    months_income.add(cursor.getInt(2));
                    dayOfMonths_income.add(cursor.getInt(3));
                    types_income.add(cursor.getInt(4));
                    accounts_income.add(cursor.getFloat(5));
                    remarks_income.add(cursor.getString(6));

                    income_type[cursor.getInt(4) - 21] += cursor.getFloat(5);
                    num_income++;
                }
            }
        }
        while (cursor.moveToNext())
        {
            if(cursor.getInt(4)<20 && GlobalVariables.selectYear==cursor.getInt(1)) {
                outcome_month[cursor.getInt(2)-1]+=cursor.getFloat(5);
                if( GlobalVariables.selectMonth==cursor.getInt(2) ) {
                    years_outcome.add(cursor.getInt(1));
                    months_outcome.add(cursor.getInt(2));
                    dayOfMonths_outcome.add(cursor.getInt(3));
                    types_outcome.add(cursor.getInt(4));
                    accounts_outcome.add(cursor.getFloat(5));
                    remarks_outcome.add(cursor.getString(6));

                    outcome_type[cursor.getInt(4) - 1] += cursor.getFloat(5);
                    num_outcome++;
                }
            }else if(GlobalVariables.selectYear==cursor.getInt(1)) {
                income_month[cursor.getInt(2)-1]+=cursor.getFloat(5);
                if (GlobalVariables.selectMonth == cursor.getInt(2)) {
                    years_income.add(cursor.getInt(1));
                    months_income.add(cursor.getInt(2));
                    dayOfMonths_income.add(cursor.getInt(3));
                    types_income.add(cursor.getInt(4));
                    accounts_income.add(cursor.getFloat(5));
                    remarks_income.add(cursor.getString(6));

                    income_type[cursor.getInt(4) - 21] += cursor.getFloat(5);
                    num_income++;
                }
            }
        }
        cursor.close();
        db.close();
    }
    private void getAxisXLables() {
        mAxisXValues=new ArrayList();
        for (int i = 0; i < 12; i++) {
            mAxisXValues.add(new AxisValue(i).setLabel(month[i]));
        }
    }
    private void getAxisPoints() {
        mPointValues =new ArrayList();
        if(type)
            for (int i = 0; i < 12; i++) {
                mPointValues.add(new PointValue(i, outcome_month[i]));
            }
        else
            for (int i = 0; i < 12; i++) {
                mPointValues.add(new PointValue(i, income_month[i]));
            }
    }
    private void initLineChart() {
        getAxisXLables();//获取x轴的标注
        getAxisPoints();//获取坐标点

        Line line;
        if(type)
            line = new Line(mPointValues).setColor(Color.parseColor("#CC6666"));
        else
            line = new Line(mPointValues).setColor(Color.parseColor("#66CC66"));
        List<Line> lines = new ArrayList<Line>();
        line.setShape(ValueShape.CIRCLE);//折线图上每个数据点的形状  这里是圆形 （有三种 ：ValueShape.SQUARE  ValueShape.CIRCLE  ValueShape.DIAMOND）
        line.setCubic(false);//曲线是否平滑，即是曲线还是折线
        line.setFilled(false);//是否填充曲线的面积
        line.setHasLabels(true);//曲线的数据坐标是否加上备注
        line.setHasLabelsOnlyForSelected(true);//点击数据坐标提示数据（设置了这个line.setHasLabels(true);就无效）
        line.setHasLines(true);//是否用线显示。如果为false 则没有曲线只有点显示
        line.setHasPoints(true);//是否显示圆点 如果为false 则没有原点只有点显示（每个数据点都是个大的圆点）
        lines.add(line);
        LineChartData data = new LineChartData();
        data.setLines(lines);

        //坐标轴
        Axis axisX = new Axis(); //X轴
        axisX.setHasTiltedLabels(true);  //X坐标轴字体是斜的显示还是直的，true是斜的显示
        axisX.setTextColor(Color.GRAY);  //设置字体颜色
        //axisX.setName("date");  //表格名称
        axisX.setTextSize(10);//设置字体大小
        axisX.setMaxLabelChars(8); //最多几个X轴坐标，意思就是你的缩放让X轴上数据的个数7<=x<=mAxisXValues.length
        axisX.setValues(mAxisXValues);  //填充X轴的坐标名称
        data.setAxisXBottom(axisX); //x 轴在底部
        //data.setAxisXTop(axisX);  //x 轴在顶部
        axisX.setHasLines(true); //x 轴分割线
        // Y轴是根据数据的大小自动设置Y轴上限(在下面我会给出固定Y轴数据个数的解决方案)
        Axis axisY = new Axis();  //Y轴
        axisY.setName("");//y轴标注
        axisY.setTextSize(10);//设置字体大小
        data.setAxisYLeft(axisY);  //Y轴设置在左边
        //data.setAxisYRight(axisY);  //y轴设置在右边
//        Axis axisY = new Axis().setHasLines(true);
//        axisY.setMaxLabelChars(6);//max label length, for example 60
//        List<AxisValue> values = new ArrayList<>();
//        for(int i = 0; i < 100; i+= 10){
//            AxisValue value = new AxisValue(i);
//            String label = "";
//            value.setLabel(label);
//            values.add(value);
//        }
//        axisY.setValues(values);
        //设置行为属性，支持缩放、滑动以及平移
        lineChart.setInteractive(true);
        lineChart.setZoomType(ZoomType.HORIZONTAL);
        lineChart.setMaxZoom((float) 2);//最大方法比例
        lineChart.setContainerScrollEnabled(true, ContainerScrollType.HORIZONTAL);
        lineChart.setLineChartData(data);
        lineChart.setVisibility(View.VISIBLE);
        /**注：下面的7，10只是代表一个数字去类比而已
         * 当时是为了解决X轴固定数据个数。见（http://forum.xda-developers.com/tools/programming/library-hellocharts-charting-library-t2904456/page2）;
         这4句代码可以设置X轴数据的显示个数（x轴0-7个数据）。
         当数据点个数小于（29）的时候，缩小到极致hellochart默认的是所有显示。
         当数据点个数大于（29）的时候。
         若不设置axisX.setMaxLabelChars(int count)这句话,则会自动适配X轴所能显示的尽量合适的数据个数。
         若设置axisX.setMaxLabelChars(int count)这句话,33个数据点测试，
         若 axisX.setMaxLabelChars(10); 里面的10大于v.right= 7; 里面的7，则 刚开始X轴显示7条数据，然后缩放的时候X轴的个数会保证大于7小于10
         若小于v.right= 7;中的7,反正我感觉是这两句都好像失效了的样子 - -! 若这儿不设置 v.right= 7; 这句话，则图表刚开始就会尽可能的显示所有数据，交互性太差*/
        Viewport v = new Viewport(lineChart.getMaximumViewport());
        v.left = 0;
        v.right = 7;
        lineChart.setCurrentViewport(v);
    }
    private int Color(int i){
        // 颜色格式 0xAABBCCDD Alpha值 R值 G值 B值
        if(type==true)
        {
            if(i%5==0)
            {
                return 0xFFCD5C5C;
            }
            if(i%5==1)
            {
                return 0xFFA52A2A;
            }
            if(i%5==2)
            {
                return 0xFFB22222;
            }
            if(i%5==3)
            {
                return 0xFF8B0000;
            }
            if(i%5==4)
            {
                return 0xFF800000;
            }
        }else{
            if(i%5==0)
            {
                return 0xFF00FF7F;
            }
            if(i%5==1)
            {
                return 0xFF3CB371;
            }
            if(i%5==2)
            {
                return 0xFF2E8B57;
            }
            if(i%5==3)
            {
                return 0xFF228B22;
            }
        }
        return ChartUtils.pickColor();
    }
    private void initPieChart(){
        //存放扇形数据的集合
        List<SliceValue> values = new ArrayList<SliceValue>();
        if(type==true)
            for (int i = 0; i < 12; i++) {
                if(outcome_type[i]>0) {
                    SliceValue sliceValue = new SliceValue(outcome_type[i], Color(i));
                    sliceValue.setLabel(GlobalVariables.typeIDTypeName(i + 1) + ":" + sliceValue.getValue() + "元");//设置label
                    values.add(sliceValue);
                }
            }
        else
            for (int i = 0; i < 4; i++) {
                if(income_type[i]>0) {
                    SliceValue sliceValue = new SliceValue(income_type[i], Color(i));
                    sliceValue.setLabel(GlobalVariables.typeIDTypeName(i + 21) + ":" + sliceValue.getValue() + "元");//设置label
                    values.add(sliceValue);
                }
            }
        data = new PieChartData(values);
        data.setHasLabels(hasLabels);
        data.setHasLabelsOnlyForSelected(hasLabelForSelected);
        data.setHasLabelsOutside(hasLabelsOutside);
        data.setHasCenterCircle(hasCenterCircle);

        if (isExploded) {
            data.setSlicesSpacing(24);
        }

        pieChart.setPieChartData(data);
    }

    @RequiresApi(api = Build.VERSION_CODES.N)
    @Override
    public void onClick(View v) {
        switch(v.getId()) {
            case R.id.btn_calendar:
                chooseDateActivity(v);
                break;
            case R.id.btn_select_type:
                if(type==true)
                {
                    btn_select_type.setText("收入");
                    type=false;
                    updateUI();
                }else
                    {
                    btn_select_type.setText("支出");
                    type=true;
                    updateUI();
                }
                break;
        }
    }
    @RequiresApi(api = Build.VERSION_CODES.N)
    public void chooseDateActivity(View v){
        Calendar calendar=Calendar.getInstance();
        new DatePickerDialog( this, new DatePickerDialog.OnDateSetListener() {
            @Override
            public void onDateSet(DatePicker view, int year, int month, int dayOfMonth) {
                GlobalVariables.selectYear = year;
                GlobalVariables.selectMonth = month+1;
                GlobalVariables.selectDayOfMonth = dayOfMonth;
                updateUI();
            }
        }
                ,calendar.get(Calendar.YEAR)
                ,calendar.get(Calendar.MONTH)
                ,calendar.get(Calendar.DAY_OF_MONTH)).show();
    }

    private void updateUI() {
        tv_date.setText(GlobalVariables.selectYear+"."+GlobalVariables.selectMonth);
        initDatabase();
        initLineChart();//初始化折线图
        initPieChart();//初始化饼状图
    }
}
